from __future__ import absolute_import, division

from gui.panda.base import *

from ..utils import Picker
from .camera import CameraController


class ViewController(Object):
    dialog  = Attribute()
    size    = Attribute()
    mouse   = Attribute()
    scene   = Attribute()
    display = Attribute()
    model   = Attribute()
    
    picker = Attribute()
    camera = Attribute()
    
    def setup(self):
        self.picker = Picker(self, self.mouse, self.scene, self.display)
        self.camera = CameraController(self.display, distance = 40, hover = 5, main_angle = 35)        
    
    def update(self):
        self.picker.update()
        
        if self.dialog.start is None:
            self.scene.setShaderInput('start', self.mouse_selection)
        else:
            self.scene.setShaderInput('start', self.dialog.start)
        
        self.scene.setShaderInput('mouse', self.mouse_selection)
        self.scene.setShaderInput('color', (0.2, 0.2, 0.2, 0))
    
    def is_occluded(self, point):
        return any(occlusion.includes(point) for occlusion in self.occlusions)
    
    @property
    def occlusions(self):
        for element in self.model.visible_elements:
            yield element.renderer.panda_area
    
    @property
    def mouse_selection(self):
        return self.picker.vector
    
    @property
    def center(self):
        return Vec4(*(self.camera.target + (0,)))
    
    def center_camera_on(self, x, y = None):
        if x is None:
            return
        
        if y is None:
            y = x.y
            x = x.x
        
        self.camera.center_on_tile(Point3(x, self.size - y + 1, 0))
    
    def center_camera_on_map(self):
        self.camera.center_on_tile(Point3(self.size / 2.0, self.size / 2.0, 0))
    
    def zoom_in(self, n = 1):
        for _ in range(n):
            self.camera.zoom_in()
    
    def zoom_out(self, n = 1):
        for _ in range(n):
            self.camera.zoom_out()
    
    def recalculate(self):
        self.camera.recalculate()
